﻿#include "rgsattributetable.h"
#include"Riskgis.h"
#include<qgsvectorlayereditbuffer.h>
#include<qgsattributedialog.h>
//#include<qgsfeatureaction.h>
#include<QHBoxLayout>
rgsattributetable::rgsattributetable(QgsVectorLayer* layer,QgsMapCanvas *mapCanvas,
                                     QgsAttributeTableFilterModel::FilterMode initialMode,
                                      Qt::WindowFlags flags,QWidget *parent,const QString &filterExpression)
    : QWidget(parent),mLayer(layer),UiWidget(new Ui::qgsattributetablebase)
{
    UiWidget->setupUi(this);
    setObjectName( QStringLiteral( "QgsAttributeTableDialog/" ) + layer->id() );
    setAttribute( Qt::WA_DeleteOnClose );
    QgsFeatureRequest r;
    bool needsGeom = false;
    if ( mLayer->geometryType() != QgsWkbTypes::NullGeometry &&
        initialMode == QgsAttributeTableFilterModel::ShowVisible )
    {
        QgsMapCanvas *mc = Riskgis::instance()->mapCanvas();
        QgsRectangle extent( mc->mapSettings().mapToLayerCoordinates( layer, mc->extent() ) );
        r.setFilterRect( extent );
        needsGeom = true;
    }
    else if ( initialMode == QgsAttributeTableFilterModel::ShowSelected )
    {
        r.setFilterFids( layer->selectedFeatureIds() );
    }
    else if ( initialMode == QgsAttributeTableFilterModel::ShowEdited )
    {
        r.setFilterFids( layer->editBuffer() ? layer->editBuffer()->allAddedOrEditedFeatures() : QgsFeatureIds() );
    }
    else if ( !filterExpression.isEmpty() )
    {
        r.setFilterExpression( filterExpression );
    }
    if ( !needsGeom )
        r.setFlags( QgsFeatureRequest::NoGeometry );
    initLayerCache(true);
    initModels(mapCanvas,r,true);

    mMainview=new QgsAttributeTableView(this);
    //mMainview=new QTableView(this);
    //mMainview->setStyleSheet()

    mMainview->setModel(mFilterModel);
    mMainview->setContentsMargins(0,0,0,0);


    mFilterModel->setAttributeTableConfig(mLayer->attributeTableConfig());
    mMainview->setAttributeTableConfig(mLayer->attributeTableConfig());

    inittiilbar();


    QVBoxLayout * Vlayout=new QVBoxLayout(this);
    //Vlayout->setMargin(0);
    Vlayout->setContentsMargins(0,0,0,0);
    Vlayout->addWidget(toolbar);
    initlineEditwidget();
    Vlayout->addWidget(selectExpressionFrame);
    Vlayout->addWidget(mMainview);
    //当为布局设置父组件后，隐式的使用了setlayout(*);
    //setLayout(Vlayout);
    resize(900,900);

    show();
}

void rgsattributetable::initLayerCache(bool cacheGeometry)
{
    mLayerCache = new QgsVectorLayerCache( mLayer, mLayer->featureCount(), this );
    mLayerCache->setCacheGeometry( cacheGeometry );
}

void rgsattributetable::initModels(QgsMapCanvas *mapCanvas, const QgsFeatureRequest &request, bool loadFeatures)
{
    mMasterModel = new QgsAttributeTableModel( mLayerCache, this );
    mMasterModel->setRequest( request );
    mMasterModel->setExtraColumns( 1 );
    if ( loadFeatures )
        mMasterModel->loadLayer();
    mFilterModel = new QgsAttributeTableFilterModel( mapCanvas, mMasterModel, mMasterModel );
    //mFeatureListModel = new QgsFeatureListModel( mFilterModel, mFilterModel );
    //mFeatureListModel->setSortByDisplayExpression( true );
}

void rgsattributetable::inittiilbar()
{
    toolbar=new QToolBar(this);

    toolbar->addAction(UiWidget->actiontest);
    UiWidget->actionactionToggleEditing->blockSignals(true);
    UiWidget->actionactionToggleEditing->setCheckable( true );
    UiWidget->actionactionToggleEditing->setChecked( mLayer->isEditable() );
    UiWidget->actionactionToggleEditing->blockSignals( false );
    toolbar->addAction(UiWidget->actionactionToggleEditing);
    connect(mLayer,&QgsVectorLayer::editingStopped,this,&rgsattributetable::actionStatus);

    toolbar->addAction(UiWidget->actionselectExpression);
    toolbar->addAction(UiWidget->actionSelect_All);
    toolbar->addAction(UiWidget->actionnvertSelection);
    toolbar->addAction(UiWidget->actionremoveSelection);
    toolbar->addAction(UiWidget->actionsetSelectedOnTop);
    toolbar->addAction(UiWidget->actionpanToSelected);
    toolbar->addAction(UiWidget->actionZoomMapToSelectedRows);
    toolbar->addSeparator();
    toolbar->setIconSize(QSize(16,16));
    toolbar->setContentsMargins(0,0,0,0);
    //QToolButton* selectall=new QToolButton(this);
    //selectall->addAction(UiWidget->actionSelect_All);

}

void rgsattributetable::initlineEditwidget()
{
    selectExpressionFrame=new QFrame(this);
    m_info=new QgsMessageBar(selectExpressionFrame);
    lineEdit=new QLineEdit(selectExpressionFrame);
    btnconfirm=new QPushButton(selectExpressionFrame);
    btnconfirm->setText("confirm");
    QVBoxLayout* vlayout=new QVBoxLayout(selectExpressionFrame);
    QHBoxLayout* hlayout=new QHBoxLayout();
    hlayout->setContentsMargins(0,0,0,0);
    vlayout->setContentsMargins(0,0,0,0);
    hlayout->addWidget(lineEdit);
    hlayout->addWidget(btnconfirm);
    vlayout->addLayout(hlayout);
    vlayout->addWidget(m_info);
    selectExpressionFrame->setContentsMargins(0,0,0,0);
    selectExpressionFrame->hide();
    connect(this,&rgsattributetable::emitmessage,m_info,&QgsMessageBar::pushInfo);
    connect(btnconfirm,&QPushButton::clicked,this,&rgsattributetable::comfirmSelectExpression);
}

void rgsattributetable::actionStatus()
{
    UiWidget->actionactionToggleEditing->blockSignals(true);
    UiWidget->actionactionToggleEditing->setCheckable( true );
    UiWidget->actionactionToggleEditing->setChecked( mLayer->isEditable() );
    UiWidget->actionactionToggleEditing->blockSignals( false );
    //更新action按钮状态
    if(mLayer->isEditable()){

    }
    else {

    }
}

void rgsattributetable::comfirmSelectExpression()
{
    QString s=lineEdit->text();
    QgsExpression mExpression=QgsExpression(s);
    qDebug()<<mExpression.parserErrorString();
    qDebug()<<mExpression.isValid();
    qDebug()<<mExpression.hasParserError();
    qDebug()<<mExpression.hasParserError();
    if(mExpression.isValid() && !mExpression.hasParserError() && !mExpression.hasEvalError()){
        qDebug()<<mExpression.expression();
    }
    else {
        qDebug()<<"has error";
        emit emitmessage("","expression error!");
    }
}

//void rgsattributetable::mouseDoubleClickEvent(QMouseEvent *event)
//{
//    //qDebug()<<"event";
////    if(!mLayer->isEditable())
////        return QWidget::event(event);
//    qDebug()<<event->type();
//    if(event->type()==QEvent::MouseButtonDblClick){
//        if(mMainview->geometry().contains(event->pos())){

//            QModelIndex positionAttritube=mMainview->indexAt(event->pos());
//            if(!positionAttritube.isValid())
//                return;
//            qDebug()<<"editline编辑";
//            viewRow=positionAttritube.row();
//            viewCol=positionAttritube.column();
//            int width=mMainview->columnWidth(viewCol);
//            int hight=mMainview->rowHeight(viewRow);
//            width=width*viewCol+mMainview->verticalHeader()->lineWidth();
//            hight=hight*viewRow+mMainview->horizontalHeader()->height();
//            if(editLine==nullptr)
//                editLine=new QLineEdit(this);
//            editLine->setGeometry(width,hight,mMainview->columnWidth(viewCol),mMainview->rowHeight(viewRow));
//            editLine->setText(positionAttritube.data().toString());
//            return ;
//        }
//        else {
//            return QWidget::mouseDoubleClickEvent(event);
//        }
//    }
//    else {
//        return QWidget::mouseDoubleClickEvent(event);
//    }
//}


void rgsattributetable::on_actionSelect_All_triggered()
{
    mLayer->selectAll();
}


void rgsattributetable::on_actionnvertSelection_triggered()
{
    mLayer->invertSelection();
}


void rgsattributetable::on_actionremoveSelection_triggered()
{
    mLayer->removeSelection();
}


void rgsattributetable::on_actionsetSelectedOnTop_toggled(bool checked)
{
    //qDebug()<<checked;
    if(checked){
        mFilterModel->setSelectedOnTop(true);
        //mMainview->repaintRequested();

    }
    else{
        mFilterModel->setSelectedOnTop(false);
    }
}


void rgsattributetable::on_actionZoomMapToSelectedRows_triggered()
{
    Riskgis::instance()->mapCanvas()->zoomToSelected(mLayer);
}


void rgsattributetable::on_actionpanToSelected_triggered()
{
    Riskgis::instance()->mapCanvas()->panToSelected(mLayer);
}


void rgsattributetable::on_actionselectExpression_triggered()
{
    if(selectExpressionFrame->isHidden()){
        selectExpressionFrame->show();
    }
    else {
        selectExpressionFrame->hide();
    }
}


void rgsattributetable::on_actiontest_triggered()
{
    qDebug()<<"添加特征测试开始";
    qDebug()<<mLayer->isEditable();
    QgsProject::instance()->startEditing( mLayer );
    qDebug()<<mLayer->isEditable();
    if(!mLayer->isEditable())
        return;
//    QgsFields s =mLayer->fields();
//    for(auto e:s){
//        qDebug()<<e.type();
//        qDebug()<<e.typeName();
//        qDebug()<<e.name();
//        //qDebug()<<e.defaultValueDefinition();
//    }
//    for(int i=0;i<s.count();i++){
//        //qDebug()<<( *sLastUsedValues() )[ mLayer ][i];
//        qDebug()<<"defaultValueClause:"<<mLayer->dataProvider()->defaultValueClause(i);
//        qDebug()<<"defaultValue:"<<mLayer->dataProvider()->defaultValue(i);
//    }
    qDebug()<<"开始编辑";

    QgsFeature f;
    QgsAttributeMap initialAttributeValues;
    QgsAttributes att;
    for(int i=0;i<mLayer->fields().count();i++){
        att.push_back(QVariant());
    }
    f.setAttributes(att);
    QgsExpressionContext context = mLayer->createExpressionContext();
    const QgsFeature newFeature = QgsVectorLayerUtils::createFeature( mLayer, f.geometry(), initialAttributeValues,
                                                                     &context );

    //需要设置属性编辑上下文信息，否则要对特征设置属性否则会出现指针悬空
    QgsAttributeDialog* dialog=new QgsAttributeDialog(mLayer,&f,false);
    //dialog->setAttribute( Qt::WA_DeleteOnClose );
    dialog->setMode( QgsAttributeEditorContext::AddFeatureMode );
    dialog->setEditCommandMessage( "Add Feature" );
//    connect(dialog,&QgsAttributeDialog::finished,this,[=](){
//        qDebug()<<"打印属性增加窗口内容";
//        for(auto e:qobject_cast<QgsAttributeDialog*>(sender())->feature()->attributes()){
//            qDebug()<<e;
//        }
//    });
    //dialog->show();
    if(dialog->exec()){
        for(auto e:dialog->feature()->attributes()){
            qDebug()<<e;
        }
        qDebug()<<"比较";
        qDebug()<<&f;
        qDebug()<<dialog->feature();
        if(&f==dialog->feature()){
            qDebug()<<"相同";
        }
    }
    else {
        qDebug()<<"dialog.exec() false";
    }
//    for(auto e:f.attributes()){
//        qDebug()<<e;
//    }
    //f=newFeature;
    delete dialog;
    qDebug()<<"特征是："<<f.isValid();

    mLayer->beginEditCommand( "11" );
    qDebug()<<mMasterModel->rowCount();
    bool mFeatureSaved = mLayer->addFeature( f );
    qDebug()<<mMasterModel->rowCount();
    if(mFeatureSaved){
        qDebug()<<"addfeature";
        mLayer->endEditCommand();
        mLayer->triggerRepaint();
    }
    else{
        mLayer->destroyEditCommand();
    }
    qDebug()<<f.id();
    mLayer->selectByIds(QgsFeatureIds()<<f.id());
    QgsFeatureIds selectids=mLayer->selectedFeatureIds();
    if(selectids.empty()){
        qDebug()<<"empty";
    }
    for(auto e: selectids){
        qDebug()<<e;
    }
    mMasterModel->reload( mMasterModel->index( 0, 0 ), mMasterModel->index( mMasterModel->rowCount() - 1, mMasterModel->columnCount() - 1 ) );
    //mMainView->setCurrentEditSelection( QgsFeatureIds() << action.feature().id() );
    mMainview->scrollToFeature( f.id() );
    qDebug()<<"end";
}


void rgsattributetable::on_actionactionToggleEditing_toggled(bool arg1)
{
    //qDebug()<<"toggled";
    if(!mLayer){
        return;
    }
    //如果属性表处于编辑状态，则现在用户再次点击了编辑按钮，意味着不在编辑，
    //此时设置属性表为不可编辑状态，属性表失去焦点，且正在编辑的内容被保存
    if ( mLayer->isEditable() && mMainview->indexWidget( mMainview->currentIndex() ) )
        mMainview->indexWidget( mMainview->currentIndex() )->setEnabled( false );


    Riskgis::instance()->toggleEditing(mLayer);

    actionStatus();
}


